package au.edu.unsw.editingtool.global;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.Hashtable;
import java.util.LinkedList;
import java.util.StringTokenizer;

import javax.servlet.http.HttpServletRequest;
import javax.xml.parsers.DocumentBuilder;
import javax.xml.parsers.DocumentBuilderFactory;
import javax.xml.parsers.ParserConfigurationException;
import javax.xml.transform.TransformerConfigurationException;
import javax.xml.transform.TransformerException;
import javax.xml.xpath.XPath;
import javax.xml.xpath.XPathConstants;
import javax.xml.xpath.XPathExpression;
import javax.xml.xpath.XPathExpressionException;
import javax.xml.xpath.XPathFactory;

import org.w3c.dom.Document;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

import au.edu.unsw.editingtool.fedora.FedoraFactory;
import au.edu.unsw.editingtool.transformxml.XMLProcessor;

public class EditingToolUtil {
	
	public static String join(String array[], String delimiter, String left, String right) {
		String result = "";
		
		if ((array == null) || (array.length == 0))
			return result;
		
		int i = 0;
		for (; i < array.length - 1; i++) {
			result += left + array[i] + right + delimiter;
		}
		
		result += left + array[i] + right;
		return result;
	}
	
	@SuppressWarnings("unchecked")
	public static Object splitString(String rawString, String delimiter, Object obj){
		
		String className = obj.getClass().getName();
		
		StringTokenizer token = new StringTokenizer(rawString, delimiter);
		
		while (token.hasMoreElements()) {
			String t = token.nextToken().trim();
			if (className.equals("java.util.Hashtable"))
				((Hashtable<String, String>) obj).put(t, null);
			else if (className.equals("java.util.LinkedList"))
				((LinkedList) obj).add(t);
		}
		
		return obj;
	}
	
	public static Hashtable<String, String> getNodeListViaPath(String path, String fileToRead) throws ParserConfigurationException, SAXException, IOException, XPathExpressionException {
		DocumentBuilderFactory dom = DocumentBuilderFactory.newInstance();
		dom.setNamespaceAware(true);
		DocumentBuilder builder = dom.newDocumentBuilder();
		Document doc = builder.parse(new File(fileToRead));
		Hashtable<String, String> results = new Hashtable<String, String>();
		
		XPathFactory factory = XPathFactory.newInstance();
		XPath xpath = factory.newXPath();
		XPathExpression expr = xpath.compile(path);
		NodeList nodes = (NodeList) expr.evaluate(doc, XPathConstants.NODESET);
		
		for (int i = 0; i < nodes.getLength(); i++)
			results.put(nodes.item(i).getNodeName(), nodes.item(i).getNodeValue());
		return results;
	}
	
	public static String transformAsLabel(String value) {
		String label[] = value.split("_");
		String result = "";
		for (int i=0; i<label.length ; i++) {
			result += Character.toUpperCase(label[i].charAt(0)) + label[i].substring(1) + " ";
		}
		return result.substring(0, result.length() - 2);
	}
	
	public static String createTempFile(String name, String suffix, String dir) throws IOException {
		File temp = File.createTempFile(name, suffix, new File(dir));
		return temp.getAbsolutePath();
	}
	
 
	public static String getValetXML(String sessionId, String pid, String datastreamID,
									 FedoraFactory fedora, EditingToolPropertyReader reader) 
	throws IOException, EditingToolException, TransformerConfigurationException, TransformerException, SAXException {
		
		String file = "";
		String valetXML = "";
		XMLProcessor processor = new XMLProcessor();
		
		file = EditingToolUtil.createTempFile(sessionId, "xml", EditingToolGlobalConstant.tempFileDir);
		
		byte[] xml = fedora.getDatastream(pid, datastreamID);
		FileOutputStream fos = new FileOutputStream(file);
		fos.write(xml);
		
		valetXML = EditingToolUtil.createTempFile(sessionId, "out", EditingToolGlobalConstant.tempFileDir);
		
		Hashtable<String, String> properties = getProperties(reader, EditingToolPropertyReader.DATASTREAM);
		
		processor.setOutFile(valetXML);
		processor.setXml(file);
		processor.setXsl(properties.get("root") + EditingToolGlobalConstant.fileSeparator +
						 properties.get("name") + EditingToolGlobalConstant.fileSeparator + 
						 properties.get("tovalet"));
		processor.xmlProcessor("");
		
		return valetXML;
	}

	public static String getHTTPRequestData(HttpServletRequest request, String mask) {
		if ((request.getParameter(mask) == null) || 
			(request.getParameter(mask).trim().length() == 0))
			return (String) request.getAttribute(mask);
		return request.getParameter(mask);
	}
	
	public static Hashtable<String, String> getProperties(EditingToolPropertyReader reader, 
													String filter) throws IOException {
		reader.clean();
		reader.setFile(filter);
		reader.retrieveProperties();
		return reader.getProperties();
	}
	
}
